﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using WowParserLib.Events;
using System.Text.RegularExpressions;
using WowParserLib.Events.PrefixArgs;
using WowParserLib.Events.SuffixArgs;
using WowParserLib.EventParsers;

namespace WowParserLib
{
    /// <summary>
    /// Creates Event objects based on the log string
    /// </summary>
    public class EventsFactory
    {
        private IEventIdProvider _eventIdProvider;

        public EventsFactory(IEventIdProvider eventIdProvider) 
        {
            _eventIdProvider = eventIdProvider;
        }

        public Event Create(string eventString, Actor source, Actor target) 
        {
            int start = eventString.IndexOf("  ");
            int end = eventString.IndexOf(",");
            string eventName = eventString.Substring(start, end - start).Trim();

            switch (eventName)
            {
                case ("SPELL_DAMAGE"):
                    return new EventParser<SpellDamage>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new DamageArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case("SPELL_PERIODIC_DAMAGE"):
                    return new EventParser<SpellPeriodicDamage>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new DamageArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case("SPELL_AURA_DISPELLED"):
                    return new EventParser<SpellAuraDispelled>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new AuraDispelledArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case("SPELL_EXTRA_ATTACKS"):
                    return new EventParser<SpellExtraAttacks>(_eventIdProvider).Parse(
    eventString, source, target,
    new IArgsParser[] { 
                            new ExtraAttacksArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_MISSED"):
                    return new EventParser<SpellMissed>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new MissedArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_HEAL"):
                    return new EventParser<SpellHeal>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new HealArgsParser(10)
                        });
                case ("RANGE_DAMAGE"):
                    return new EventParser<RangeDamage>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new RangeEventArgsParser(7),
                            new DamageArgsParser(10)
                        });
                case ("SPELL_PERIODIC_HEAL"):
                    return new EventParser<SpellPeriodicHeal>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new HealArgsParser(10)
                        });
                case ("SPELL_ENERGIZE"):
                    return new EventParser<SpellEnergize>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new EnergizedArgsParser(10)
                        });
                case ("SPELL_SUMMON"):
                    return new EventParser<SpellSummon>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_PERIODIC_ENERGIZE"):
                    return new EventParser<SpellPeriodicEnergize>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new EnergizedArgsParser(10), 
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_CAST_START"):
                    return new EventParser<SpellCastStart>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_AURA_APPLIED"):
                    return new EventParser<SpellAuraApplied>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new AuraAppliedArgsParser(10)
                        });
                case ("SPELL_AURA_REMOVED"):
                    return new EventParser<SpellAuraRemoved>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new AuraRemovedArgsParser(10)
                        });
                case ("SPELL_AURA_APPLIED_DOSE"):
                    return new EventParser<SpellAuraApplied>(_eventIdProvider).Parse(
    eventString, source, target,
    new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new AuraAppliedDoseArgsParser(10)
                        });
                case ("SPELL_AURA_REMOVED_DOSE"):
                    return new EventParser<SpellAuraApplied>(_eventIdProvider).Parse(
    eventString, source, target,
    new IArgsParser[] { 
                            new SpellEventArgsParser(7),
                            new AuraRemovedArgsParser(10)
                        });
                case ("SPELL_CAST_FAILED"):
                    return new EventParser<SpellCastFailed>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new CastFailedArgsParser(10),
                            new SpellEventArgsParser(7) 
                        });
                case ("SPELL_CAST_SUCCESS"):
                    return new EventParser<SpellCastSuccess>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new SpellEventArgsParser(7) 
                        });

                case ("SWING_DAMAGE"):
                    return new EventParser<SwingDamage>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new DamageArgsParser(7)
                        });
                case ("SWING_MISSED"):
                    return new EventParser<SwingMissed>(_eventIdProvider).Parse(
                        eventString, source, target,
                        new IArgsParser[] { 
                            new MissedArgsParser(7)
                        });
                case ("PARTY_KILL"):
                    return new EventParser<PartyKill>(_eventIdProvider).Parse(
                        eventString, source, target);
                case ("UNIT_DIED"):
                    return new EventParser<UnitDied>(_eventIdProvider).Parse(
                        eventString, source, target);
                default:
                    return new EventParser<NullEvent>(_eventIdProvider).Parse(
                        eventString, source, target, new IArgsParser[] { new NullPrefixArgsParser(0) });
            }
        }

    }
}
